Fermer

juin 11, 2025

Examiner les API dans .NET Maui Community Toolkit Essentials

Examiner les API dans .NET Maui Community Toolkit Essentials


Dans cet article, vous en apprendrez sur .NET Maui Community Toolkit Essentials, un ensemble d’API multiplateformes qui vous permettent d’effectuer facilement des opérations communes. Commençons!

Comme mentionné dans l’introduction, .NET Maui Community Toolkit Essentials (ci-après Essentials) est une API multiplateforme qui fonctionne avec n’importe quelle application .NET MAUI et peut être accessible via un code partagé, quelle que soit la façon dont l’interface graphique a été créée.

Les API disponibles sont:

  • Ressources d’appthéme: Permet de créer des ressources adaptées au thème qui changent automatiquement avec le thème de l’appareil.
  • Badge: Permet de définir un nombre sur le badge de l’icône de l’application sur l’écran d’accueil.
  • Pivot: Permet de sélectionner un dossier dans l’appareil.
  • Fichier: Permet d’enregistrer un fichier dans le système de fichiers de l’appareil.
  • Discours: Convertit la voix d’un enregistrement en texte.

Voyons comment utiliser les API ci-dessus dans un projet pratique.

Créer un projet de pratique

Nous allons créer une application qui utilise des fonctionnalités essentielles. Pour ce faire, suivez ces étapes:

  1. Créer un projet en sélectionnant le Application .net Maui modèle sans inclure le contenu de l’échantillon.
  2. Installer Progress Telerik UI pour .Net Maui Contrôles dans le projet en suivant le guide d’installation. Dans mon cas, je préfère utiliser l’installation du package NuGet. Les contrôles Telerik nous permettent de personnaliser facilement l’apparence de l’application.
  3. Installer le CommunityToolkit.Maui et Microsoft.Maui.Controls.Compatibility Packages dans votre projet .net Maui.
  4. Dans le MauiProgram.cs fichier, ajouter des appels au UseTelerik et UseMauiCommunityToolkit Méthodes comme suit:
public static class MauiProgram
{
    public static MauiApp CreateMauiApp()
    {
        var builder = MauiApp.CreateBuilder();
        builder
            .UseMauiApp<App>()
            .UseMauiCommunityToolkit()
            .UseTelerik()
            ...

        return builder.Build();
    }
}
  1. Dans le MainPage.xaml Fichier, remplacez le contenu contenu par ce qui suit:
<ContentPage ...
    xmlns:telerik="clr-namespace:Telerik.Maui.Controls;assembly=Telerik.Maui.Controls"
    xmlns:toolkit="http://schemas.microsoft.com/dotnet/2022/maui/toolkit"
    Shell.NavBarIsVisible="False">

    <ScrollView>
        <VerticalStackLayout
            Padding="20"
            HorizontalOptions="Center"
            Spacing="20"
            VerticalOptions="Center">
            <Label
                FontAttributes="Bold"
                FontSize="24"
                HorizontalOptions="Center"
                Text="My Voice Diary"
                TextColor="{AppThemeBinding Light=Black,
                                            Dark=#DDD}" />
            <Label
                FontSize="14"
                HorizontalTextAlignment="Center"
                Opacity="0.8"
                Text="Press 'Start Recording' and dictate your diary entry. Then, press 'Stop Recording' to generate the transcription."
                TextColor="{AppThemeBinding Light=Black,
                                            Dark=#DDD}" />
            <telerik:RadBorder
                x:Name="frmTranscription"
                Padding="15"
                BorderColor="#CCCCCC"
                BorderThickness="2"
                CornerRadius="10">
                <VerticalStackLayout Spacing="5">
                    <Label
                        FontAttributes="Bold"
                        FontSize="16"
                        Text="Transcription:"
                        TextColor="{AppThemeBinding Light=Black,
                                                    Dark=#DDD}" />
                    <Label
                        x:Name="lblDiary"
                        FontSize="14"
                        Text="You haven't recorded anything yet..."
                        TextColor="{AppThemeBinding Light=#333333,
                                                    Dark=#DDD}" />
                </VerticalStackLayout>
            </telerik:RadBorder>
            <Label
                x:Name="lblStatus"
                FontSize="14"
                HorizontalOptions="Center"
                HorizontalTextAlignment="Center"
                IsVisible="False"
                Text=""
                TextColor="Green" />
            <telerik:RadButton
                x:Name="btnStart"
                BackgroundColor="#4CAF50"
                Clicked="BtnStartRecording_Clicked"
                CornerRadius="20"
                HorizontalOptions="Center"
                Text="Start Recording"
                TextColor="White" />
            <telerik:RadButton
                x:Name="btnPickFolder"
                BackgroundColor="#2196F3"
                Clicked="BtnPickFolder_Clicked"
                CornerRadius="20"
                HorizontalOptions="Fill"
                Text="Select Folder"
                TextColor="White" />
            <telerik:RadButton
                x:Name="btnSaveFile"
                BackgroundColor="#FB8C00"
                Clicked="BtnSaveFile_Clicked"
                CornerRadius="20"
                HorizontalOptions="Fill"
                Text="Save Transcription File"
                TextColor="White" />
            <Label
                x:Name="lblSelectedFolder"
                FontSize="12"
                HorizontalOptions="Center"
                Opacity="0.7"
                Text="No folder selected."
                TextColor="{DynamicResource PrimaryTextColor}" />
        </VerticalStackLayout>
    </ScrollView>
</ContentPage>
  1. Remplacez le contenu de code du fichier de code, c’est-à-dire le contenu de MainPage.xaml.cs– avec ce qui suit:
public partial class MainPage : ContentPage
{
    public MainPage()
    {
        InitializeComponent();
    }

    private async void BtnStartRecording_Clicked(object sender, EventArgs e)
    {
    }

    private async void BtnPickFolder_Clicked(object sender, EventArgs e)
    {
    }

    private async void BtnSaveFile_Clicked(object sender, EventArgs e)
    {
    }
}

Lorsque vous exécutez l’application avec les étapes précédentes implémentées, nous aurons une belle interface graphique dans des thèmes sombres et légers:

L'exemple d'application est une application de prise de notes vocale où nous implémenterons les API Essentials

Voyons maintenant comment implémenter les éléments essentiels dans l’application.

Implémentation de ressources AppTheme

Si vous avez travaillé avec le AppThemeBinding Extension pour définir des valeurs en fonction du thème sélectionné par l’utilisateur (comme dans notre exemple d’application), vous pouvez avoir rencontré des situations où vous deviez définir la même valeur pour le Light et Dark Propriétés dans plusieurs contrôles.

S’il est vrai que vous pouvez simplifier ce processus en créant des dictionnaires et des styles de ressources, il pourrait arriver un moment où vous souhaitez réutiliser une ressource avec Light, Dark et Default Propriétés, centraliser ces valeurs en un seul endroit. Cela peut être réalisé en utilisant AppThemeObject et AppThemeColor De l’essentiel, qui vous permettent de créer des ressources consacrées au thème pour vos applications qui s’adaptent au thème de l’appareil de l’utilisateur.

Il convient de noter que AppThemeObject et AppThemeColor sont construits sur les concepts de AppThemeBindingce qui leur permet d’être utilisé dans un dictionnaire de ressources.

Création d’appthemeObject

AppThemeObject est un objet générique au thème qui vous permet de définir n’importe quelle valeur sur le Light, Dark et Default propriétés. Par exemple, supposons que dans notre application, nous voulons stocker les valeurs de logo dans un dictionnaire de ressources que vous réutiliserez à plusieurs reprises. Définissons un AppThemeObject Ressource, à laquelle nous pouvons attribuer n’importe quelle valeur comme suit:

<ContentPage.Resources>
    <toolkit:AppThemeObject
        x:Key="Logo"
        Dark="logo_dark.png"
        Light="logo_light.png" />
</ContentPage.Resources>

Il est important de noter que l’objet défini doit être compatible avec la propriété attribuée; Sinon, une exception sera lancée.

Ensuite, nous pouvons réutiliser la ressource de n’importe quel Image contrôle à l’aide AppThemeResource et référence à la ressource comme suit:

<Image Source="{toolkit:AppThemeResource Logo}" WidthRequest="150" />

Avec le code ci-dessus implémenté, nous voyons le logo affiché dans l’application, qui change en fonction du thème sélectionné par l’utilisateur:

Création d'une ressource réutilisable à l'aide d'AppTheMeObject et AppthemeResource

Maintenant, voyons comment créer AppThemeColor objets.

Création d’AppthemeColor

AppThemeColor est un type de couleur spécialisé et consacré à un thème qui vous permet de définir une couleur pour le Light, Dark et Default propriétés. Dans l’exemple d’application, nous remplacerons l’utilisation de AppThemeBinding avec AppThemeResource. Pour ce faire, nous créerons un AppThemeColor Ressource dans les ressources de contenu comme suit:

<ContentPage.Resources>
    <toolkit:AppThemeObject
        x:Key="Logo"
        Dark="logo_dark.png"
        Light="logo_light.png" />
    <toolkit:AppThemeColor
        x:Key="TextColor"
        Dark="#DDD"
        Light="Black" />
</ContentPage.Resources>

Ensuite, nous remplacerons les références où nous trouvons l’utilisation de AppThemeBinding avec l’utilisation de AppThemeResource faisant référence au AppThemeColor ressource:

<Label
    FontAttributes="Bold"
    FontSize="24"
    HorizontalOptions="Center"
    Text="My Voice Diary"
    TextColor="{toolkit:AppThemeResource TextColor}" />

Bien qu’il n’y ait pas de modifications visuelles à l’interface, nous aurons centralisé la ressource couleur, ce qui lui permet d’être appliqué non seulement à un seul contrôle mais à tout contrôle que nous voulons, comme un Button, Entryetc.

Sélectionner facilement des dossiers avec Folderpicker

Le FolderPicker La classe est extrêmement utile lorsque nous devons sélectionner un dossier sur l’appareil. Pour l’utiliser, nous devons activer les autorisations correspondantes en suivant le guide de documentation. Par exemple, pour Android, nous devons configurer l’autorisation suivante dans le manifeste:

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />

Une fois les autorisations nécessaires à configurer, nous pouvons utiliser le PickAsync Méthode de la FolderPicker classe directement si nécessaire comme suit:

var result = await FolderPicker.Default.PickAsync(cancellationToken);

Dans la méthode ci-dessus, PickAsync est la méthode qui permet la sélection des dossiers et demande également automatiquement l’autorisation d’y accéder. Le résultat de l’exécution renvoie un FolderPickResult Tapez avec les propriétés suivantes:

  • Folder (Dossier): le dossier sélectionné
  • Exception (Exception): Si l’opération échoue, renvoie l’exception
  • IsSuccessful (bool): indique si l’exécution a réussi

Une autre façon d’utiliser PickAsync est en enregistrant le service en singleton dans MauiProgram.cs comme suit:

public static class MauiProgram
{
    public static MauiApp CreateMauiApp()
    {
        var builder = MauiApp.CreateBuilder();
        ...
#if DEBUG
        builder.Logging.AddDebug();
#endif
        builder.Services.AddSingleton<IFolderPicker>(FolderPicker.Default);

        return builder.Build();
    }
}

Avec cela, nous pouvons injecter la dépendance partout où cela est nécessaire, dans notre cas, dans le MainPage constructeur:

public partial class MainPage : ContentPage
{
    private readonly IFolderPicker folderPicker;
    private string? selectedFolderPath;
    public MainPage(IFolderPicker folderPicker)
    {
        InitializeComponent();
        this.folderPicker = folderPicker;
    }
    ...
}

Enfin, la mise en œuvre du gestionnaire d’événements pour le btnPickFolder Le bouton aura l’air comme suit:

private async void BtnPickFolder_Clicked(object sender, EventArgs e)
{
    lblStatus.IsVisible = false;
    var result = await folderPicker.PickAsync(CancellationToken.None);            
    if (result.IsSuccessful)
    {
        selectedFolderPath = result.Folder.Path;
        lblSelectedFolder.Text = $"Selected Folder:
{selectedFolderPath}";
        await Toast.Make("Folder selected successfully").Show();
    }
    else
    {
        await Toast.Make($"
Error selecting folder: {result.Exception?.Message}").Show();
    }
}

Le résultat de l’exécution de l’application avec le changement ci-dessus ressemblera à ceci:

Sélection d'un dossier à l'aide de Folderpicker

Maintenant, voyons comment enregistrer des fichiers en utilisant FileSaver.

Enregistrement de fichiers dans .net Maui à l’aide de fichiers

FileSaver est une classe qui permet de sélectionner l’emplacement pour enregistrer un fichier, quel que soit le système d’exploitation utilisé. Vous pouvez voir les autorisations requises pour chaque système d’exploitation dans le documentation officielle. Par exemple, pour enregistrer des fichiers à l’aide d’Android, vous devez activer les autorisations suivantes:

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

La façon d’enregistrer un fichier est en utilisant le SaveAsync Méthode de la FileSaver classe, que vous pouvez utiliser directement comme suit:

var fileSaverResult = await FileSaver.Default.SaveAsync("test.txt", stream, cancellationToken);

Dans le code ci-dessus, le SaveAsync La méthode permet de sélectionner l’emplacement où un fichier sera enregistré dans le système de fichiers, tout en demandant l’autorisation nécessaire si nécessaire. Nous pouvons accéder au résultat de l’exécution SaveAsync à travers les propriétés suivantes:

  • FilePath (String): fournit l’emplacement sur le disque où le fichier a été enregistré.
  • Exception (Exception): Fournit des informations dans le cas où une exception se produit pendant l’exécution de la méthode.
  • IsSuccessful (Bool): fournit une valeur booléenne pour déterminer si l’opération a réussi.

Comme avec FolderPickeril est possible d’enregistrer une instance singleton de FileSaver dans MauiProgram.cs Pour l’injecter si nécessaire, comme suit:

public static class MauiProgram
{
    public static MauiApp CreateMauiApp()
    {
        ...
        builder.Services.AddSingleton<IFolderPicker>(FolderPicker.Default);
        builder.Services.AddSingleton<IFileSaver>(FileSaver.Default);

        return builder.Build();
    }
}

Dans notre exemple, nous injectons la référence dans le MainPage constructeur:

public partial class MainPage : ContentPage
{
    private readonly IFolderPicker folderPicker;
    private string? selectedFolderPath;

    private readonly IFileSaver fileSaver;

    public MainPage(
        IFolderPicker folderPicker,
        IFileSaver fileSaver)
    {
        InitializeComponent();
        this.folderPicker = folderPicker;
        this.fileSaver = fileSaver;
    }
}

Enfin, nous ajoutons la logique au gestionnaire d’événements pour le btnSaveFile bouton:

private async void BtnSaveFile_Clicked(object sender, EventArgs e)
{
    lblStatus.IsVisible = false;
    if (string.IsNullOrWhiteSpace(selectedFolderPath))
    {
        await Toast.Make("Please select a folder before saving.").Show();
        return;
    }
    
    string diaryContent = lblDiary.Text ?? string.Empty;
    if (string.IsNullOrWhiteSpace(diaryContent) || diaryContent == "You haven't recorded anything yet..." || diaryContent == "Say your diary entry!")
    {
        await Toast.Make("There's no text to save.").Show();
        return;
    }
    
    using var stream = new MemoryStream(Encoding.UTF8.GetBytes(diaryContent));
    
    var fileName = $"Diary_{DateTime.Now:yyyy-MM-dd_HH-mm-ss}.txt";            
    var saveResult = await fileSaver.SaveAsync(fileName, stream, default);

    if (saveResult.IsSuccessful)
    {
        await Toast.Make($"File saved at: {saveResult.FilePath}").Show();
    }
    else
    {
        await Toast.Make($"Error saving file: {saveResult.Exception?.Message}").Show();
    }
}

Le code ci-dessus nous permet d’enregistrer une transcription d’un enregistrement vocal.

Discours natif en texte en utilisant les éléments essentiels

Essentials rend très simple à extraire le texte d’un enregistrement audio. Tout d’abord, activez les autorisations selon la plate-forme sur laquelle vous travaillez en suivant le documentation officielle. Pour Android, vous devez ajouter l’autorisation suivante:

<uses-permission android:name="android.permission.RECORD_AUDIO" />

Ensuite, nous pouvons demander l’autorisation de l’utilisateur pour enregistrer l’audio RequestPermissions Méthode de la SpeechToText classe:

var isGranted = await SpeechToText.Default.RequestPermissions();

Le résultat de RequestPermissions est une valeur booléenne indiquant si l’autorisation a été accordée avec succès. Sinon, nous pouvons informer l’utilisateur que l’autorisation a été refusée comme suit:

if (!isGranted)
{
    await Toast.Make("Permission not granted").Show(CancellationToken.None);
    return;
}

Si l’utilisateur accorde une autorisation, nous pouvons utiliser le ListenAsync Méthode pour démarrer le processus d’enregistrement et d’extraction de texte comme suit:

var recognitionResult = await SpeechToText.Default.ListenAsync(
                        CultureInfo.CurrentCulture,
                        new Progress<string>(partialText =>
                        {
                            Debug.WriteLine(partialText);
                        }));

Tu peux voir ça ListenAsync prend deux paramètres: le premier à déterminer la langue de l’orateur, et le second de type IProgresspermet d’effectuer une action avec le texte partiellement reconnu. Si vous voulez travailler uniquement avec le texte final, vous pouvez utiliser le résultat d’exécution. Dans notre cas, nous stockons le résultat dans le recognitionResult variable:

if (recognitionResult.IsSuccessful)
{
    Debug.WriteLine(recognitionResult.Text);
}
else
{
    await Toast.Make(recognitionResult.Exception?.Message ?? "Unable to recognize speech").Show(CancellationToken.None);
}

Il est également possible d’utiliser l’injection de dépendance avec SpeechToText. Pour ce faire, nous devons enregistrer une instance singleton de SpeechToText comme suit MauiProgram.cs:

public static class MauiProgram
{
    public static MauiApp CreateMauiApp()
    {
        ...
        builder.Services.AddSingleton<IFolderPicker>(FolderPicker.Default);
        builder.Services.AddSingleton<IFileSaver>(FileSaver.Default);
        builder.Services.AddSingleton<ISpeechToText>(SpeechToText.Default);

        return builder.Build();
    }
}

Ensuite, nous injectons la référence dans le MainPage constructeur:

public partial class MainPage : ContentPage
{
    private readonly IFolderPicker folderPicker;
    private string? selectedFolderPath;

    private readonly IFileSaver fileSaver;
    private readonly ISpeechToText speechToText;
    private StringBuilder _diaryTextBuilder = new();

    public MainPage(
        IFolderPicker folderPicker,
        IFileSaver fileSaver,
        ISpeechToText speechToText)
    {
        InitializeComponent();
        this.folderPicker = folderPicker;
        this.fileSaver = fileSaver;
        this.speechToText = speechToText;
    }
}

Enfin, nous utilisons les connaissances antérieures pour remplir le gestionnaire d’événements pour le btnStartRecording bouton comme suit:

private async void BtnStartRecording_Clicked(object sender, EventArgs e)
{            
    _diaryTextBuilder.Clear();
    lblDiary.Text = "Waiting for dictation...";
    lblStatus.IsVisible = false;
    
    bool isGranted = await speechToText.RequestPermissions(CancellationToken.None);
    if (!isGranted)
    {
        await Toast.Make("Permission not granted").Show();
        return;
    }
    var recognitionResult = await speechToText.ListenAsync(
                                CultureInfo.CurrentCulture,
                                new Progress<string>(partialText =>
                                {
                                    lblDiary.Text = partialText + " ";
                                }), CancellationToken.None);

    if (recognitionResult.IsSuccessful)
    {
        lblDiary.Text = recognitionResult.Text;
    }
    else
    {
        await Toast.Make(recognitionResult.Exception?.Message ?? "Unable to recognize speech").Show(CancellationToken.None);
    }
}

Avec le code ci-dessus, nous pouvons commencer à enregistrer la voix d’une personne et obtenir le texte comme il parle, comme indiqué dans l’image suivante:

L'application montrant comment obtenir du texte à partir d'un enregistrement vocal

Conclusion

Tout au long de cet article, vous avez appris sur .NET Maui Community Toolkit Essentials et ses principales fonctionnalités. Vous avez vu comment utiliser le AppThemeObject et AppThemeColor Classes pour centraliser les ressources qui dépendent du thème sélectionné par l’utilisateur. De même, vous avez vu comment sélectionner des dossiers et enregistrer des fichiers en utilisant FolderPicker et FileSaver. Enfin, vous avez appris à extraire du texte d’un enregistrement en utilisant SpeechToText.

Sans aucun doute, ces fonctionnalités vous permettront de créer des applications incroyables pour vos utilisateurs. Il est temps de commencer et d’ajouter ces capacités à vos propres applications.


Prêt à essayer Telerik UI pour .net Maui?

Essayer maintenant




Source link